home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Language/OS - Multiplatform Resource Library
/
LANGUAGE OS.iso
/
cpp_libs
/
rwvector.lha
/
RWVector2.1
/
src
/
xvec.cc
< prev
next >
Wrap
C/C++ Source or Header
|
1989-08-18
|
5KB
|
246 lines
/*
* Definitions for <T>Vec
*
* Copyright (C) 1988, 1989.
*
* Dr. Thomas Keffer
* Rogue Wave Associates
* P.O. Box 85341
* Seattle WA 98145-1341
*
* Permission to use, copy, modify, and distribute this
* software and its documentation for any purpose and
* without fee is hereby granted, provided that the
* above copyright notice appear in all copies and that
* both that copyright notice and this permission notice
* appear in supporting documentation.
*
* This software is provided "as is" without any
* expressed or implied warranty.
*
*
* @(#)xvec.cc 2.1 8/18/89
*/
#define NO_VECTOR_MATHFUN
#include "rw/<T>Vec.h"
#define TYPE <T>_TYPE
#include "vecdefs.h"
#if TYPE==DComplex_TYPE
#include "rw/<P>Vec.h"
#endif
#if NEEDS_OVERLOAD
overload <T>Copy;
#endif
inline void
<T>Copy(register const <T>* src, register <T>* dst, register int n)
// Copy n <T> elements from src to dst with stride of 1
{
while (n--) *dst++ = *src++;
}
inline void
<T>Copy(register const <T>* src, register int str,
register <T>* dst, register int n)
// Copy n <T> elements from src to dst with stride str
{
while (n--){
*dst++ = *src; src += str;
}
}
inline void
<T>Copy(register const <T>* src, register int srcstr,
register <T>* dst, register int dststr, register int n)
{
while (n--){
*dst = *src; src += srcstr; dst += dststr;
}
}
<T>Vec::<T>Vec()
{
block = new <T>Block(0);
npts = 0;
step = 1;
begin = block->data();
}
<T>Vec::<T>Vec(unsigned n)
{
block = new <T>Block(n);
npts = n;
step = 1;
begin = block->data();
}
<T>Vec::<T>Vec(unsigned n, <T> val)
{
block = new <T>Block(n, val);
npts = n;
step = 1;
begin = block->data();
}
<T>Vec::<T>Vec(unsigned n, <T> val, <T> by)
{
block = new <T>Block(n, val, by);
npts = n;
step = 1;
begin = block->data();
}
#if TYPE==DComplex_TYPE || TYPE==FComplex_TYPE
<T>Vec::<T>Vec(const <P>Vec& re)
{
register int nn = npts = re.length();
block = new <T>Block(nn);
step = 1;
register <T>* cp = begin = block->data();
register <P>* rp = re.data();
register int rstride = re.stride();
while(nn--){ *cp++ = <T>(*rp); rp += rstride; }
}
<T>Vec::<T>Vec(const <P>Vec& re, const <P>Vec& im)
{
register int nn = npts = re.length();
lengthCheck(im.length());
block = new <T>Block(nn);
step = 1;
register <T>* cp = begin = block->data();
register <P>* rp = re.data();
register <P>* ip = im.data();
register int rstride = re.stride();
register int istride = im.stride();
while(nn--){
*cp++ = <T>(*rp, *ip);
rp += rstride;
ip += istride;
}
}
#endif
<T>Vec::<T>Vec(const <T>Vec& a)
{
block = a.block;
block->add_reference();
npts = a.npts;
begin = a.begin;
step = a.step;
}
<T>Vec::<T>Vec(const <T>* dat, unsigned n)
{
npts = n;
block = new <T>Block(n);
step = 1;
<T>Copy(dat, begin = block->data(), n);
}
<T>Vec::<T>Vec(<T>Vec& v, int start, unsigned n, int str)
{
int maxv = v.length()-1; // Last subscript in v
int maxslice = start + (n-1)*str; // Last subscript in slice
if(start<0 || start>maxv || maxslice<0 || maxslice>maxv)
sliceErr(v.length(), start, n, str);
block = v.block;
block->add_reference();
begin = v.begin + start*v.step;
npts = n;
step = str*v.step;
}
<T>Vec::~<T>Vec()
{
delete block;
}
<T>Vec
<T>Vec::slice(int start, unsigned n, int str)
{
<T>Vec temp(*this, start, n, str);
return temp;
}
<T>Vec&
<T>Vec::operator=(const <T>Vec& a)
{
lengthCheck(a.length());
<T>Copy(a.begin, a.step, begin, step, npts);
return *this;
}
<T>Vec&
<T>Vec::operator=(<T> d)
{
register int n = length();
register <T>* tp = data();
register int tj = stride();
REGISTER <T> dd = d;
while(n--){
*tp = dd; tp += tj;
}
return *this;
}
<T>Vec&
<T>Vec::reference(<T>Vec& v)
{
delete block; // Detach from old block
block = v.block; // Attach new block
block->add_reference();
npts = v.npts;
step = v.step;
begin = v.begin;
return *this;
}
// Return copy of self with distinct instance variables
<T>Vec
<T>Vec::deepCopy()
{
<T>Vec temp(npts);
<T>Copy(begin, step, temp.data(), npts);
return temp;
}
// Guarantee that references==1 and stride==1
void
<T>Vec::deepenShallowCopy()
{
if(block->references() > 1 || stride() != 1 || begin != block->data() ){
<T>Block* newblock = new <T>Block(npts);
<T>Copy(begin, step, newblock->data(), npts);
delete block; // Detach old block
block = newblock;
step = 1;
begin = block->data();
}
}
void
<T>Vec::resize(unsigned N)
{
if(N != npts){
<T>Block* newblock = new <T>Block(N);
// Copy over old stuff.
int newLength = min( int(npts), int(N) );
<T>Copy(begin, step, newblock->data(), newLength );
delete block; // Disconnect from old block
block = newblock;
step = 1;
begin = block->data();
// If vector has grown, zero out the extra storage
unsigned hold = npts;
npts = N;
if(hold<N)slice(hold, N-hold, 1) = <T>(0);
}
}